#include <stdio.h>
#include "ohos_init.h"
#include "cmsis_os2.h"
#include "iot_gpio.h"
#include "hi_io.h"
#include "iot_pwm.h"
#include "hi_pwm.h"
#include "hi_time.h"

int count1=0;
//音符对照表：
//https://www.cnblogs.com/developer-huawei/p/13959852.html
static const uint16_t g_tuneFreqs[]={
0,
38223, // 1 1046.5,-
34052, // 2 1174.7,--
30338, // 3 1318.5,--
28635, // 4 1396.4,--
25511, // 5 1568,---
22728, // 6 1760,---
20249, // 7 1975.5,---
51021,// 8,5_低音 783.99, 40M=40*1000*1000, 40M/783.99=51021
45454,// 9,6_ 880.00
40495,// 10,7_ 987.77
};
static const uint8_t g_scoreNotes[] = {
// 《两只老虎》简谱：http://www.jianpu.cn/pu/33/33945.htm
1, 2, 3, 1, 1, 2, 3, 1, 3, 4, 5, 3, 4, 5,
5, 6, 5, 4, 3, 1, 5, 6, 5, 4, 3, 1, 1, 8, 1, 1, 8, 1,
};
// 曲谱时值
static const uint8_t g_scoreDurations[] = {
4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 8, 4, 4, 8,
3, 1, 3, 1, 4, 4, 3, 1, 3, 1, 4, 4, 4, 4, 8, 4, 4, 8,
};

// 蜂鸣器初始化函数
static void beepInit()
{
    hi_gpio_init();
    hi_io_set_func(HI_IO_NAME_GPIO_11, HI_IO_FUNC_GPIO_11_PWM2_OUT);
    hi_io_set_pull(HI_IO_NAME_GPIO_11, HI_IO_PULL_UP);
    //
    hi_pwm_init(HI_PWM_PORT_PWM2);
    hi_pwm_set_clock(PWM_CLK_XTAL);
}

// 蜂鸣器发声任务函数
static void beepSingTask(void *arg)
{
    uint32_t tune;
    uint16_t freqDivisor;
    uint32_t tuneInterval;

    beepInit();

    for (size_t i = 0; i < sizeof(g_scoreNotes) / sizeof(g_scoreNotes[0]); i++)
    {
        tune = g_scoreNotes[i]; // 简谱标记
        freqDivisor = g_tuneFreqs[tune]; // 对应的频率
        tuneInterval = g_scoreDurations[i] * (125 * 1000); // 声音的延迟
        printf("num=%d, freqDivisor=%d\n", i, freqDivisor);
        hi_pwm_start(HI_PWM_PORT_PWM2, freqDivisor / 2, freqDivisor);
        hi_udelay(tuneInterval);
        hi_pwm_stop(HI_PWM_PORT_PWM2);
    }
}

// 蜂鸣器入口函数
static void BeepEntry(void)
{
    osThreadAttr_t attr = {0};
    attr.name = "beepSingTask";
    attr.stack_size = 4096 * 2;
    attr.priority = osPriorityNormal;
    if (osThreadNew(beepSingTask, NULL, &attr) == NULL)
    {
        printf("[GpioEntry] create GpioTask failed!\n");
    }
    
}
SYS_RUN(BeepEntry);